/* eslint-disable prettier/prettier */
import * as THREE from 'three';
const textureCube = new THREE.CubeTextureLoader()
  .setPath('hdrimg/')
  .load(['px.jpg', 'nx.jpg', 'py.jpg', 'ny.jpg', 'pz.jpg', 'nz.jpg']);
// 处理svg格式数据,将svg安装要求挤压成为立体模型
const svgSqueezeHeight = (
  shapes,
  y = 0,
  height = 1,
  material,
  path,
  border = false,
  line = false,
  name
) => {
  for (let j = 0; j < shapes.length; j++) {
    const shape = shapes[j];
    // 判断为线的时候进行处理
    if (line) {
      shape.autoClose = true;
      const points = shape.getPoints();
      const geometry = new THREE.BufferGeometry().setFromPoints(points);
      const line = new THREE.Line(geometry, material);
      line.rotation.x = Math.PI / 2;
      line.position.y = y;
      return line;
    } else {
      //不是线的时候的处理
      const geometry = new THREE.ExtrudeGeometry(shape, heightSetting(height));
      const mesh = new THREE.Mesh(geometry, material);
      if (name) {
        mesh.name = name;
      }
      mesh.rotation.x = Math.PI / 2;
      mesh.position.y = y;
      if (border) {
        const edges = new THREE.EdgesGeometry(mesh.geometry, 45);
        const edgesMaterial = new THREE.LineBasicMaterial({
          color: path.color,
          transparent: true,
          opacity: 0.5,
          depthWrite: false,
        });
        const line = new THREE.LineSegments(edges, edgesMaterial);
        mesh.add(line);
      }
      return mesh;
    }
  }
};

const svgToModel = (data, name, id, spiritName) => {
  const paths = data.paths;
  let textList, iconList, svgName, exHeight, path;
  const spiritgroup = new THREE.Group();
  spiritgroup.name = spiritName;
  const svgGroup = new THREE.Group();
  svgGroup.position.y = id * 200 - 200;
  svgGroup.name = name;
  // 文字转换为精灵图
  if (data.xml.children.text) {
    textList = data.xml.children.text.children;
    for (let i = 0; i < textList.length; i++) {
      const value = textList[i].attributes;
      const text = textList[i].innerHTML;
      const textPosition = svgAttrbute(value);
      const isText = true;
      if (textPosition) {
        spiritgroup.add(addSprite(text, textPosition, isText));
      }
    }
  }
  // 图标转换为精灵图
  if (data.xml.children.icon) {
    iconList = [...data.xml.children.icon.children];
    for (let i = 0, len = iconList.length; i < len; i++) {
      const iconName = iconList[i].firstElementChild.innerHTML;
      const iconPosition = svgAttrbute(
        iconList[i].firstElementChild.attributes
      );
      if (iconPosition) {
        spiritgroup.add(addSprite(iconName, iconPosition));
      }
    }
  }
  // 处理点线面将点线面转换为立体模型
  for (let i = 0; i < paths.length; i++) {
    path = paths[i];
    const svgNameList =
      path.userData.node.parentNode.id.split('_') ||
      path.userData.node.parentNode.id; // 获取相应的svgname
    if (svgNameList.length > 0) {
      svgName = svgNameList[0];
    }
    // 面材质
    const material = new THREE.MeshStandardMaterial({
      color: path.color,
      side: THREE.DoubleSide,
      // emissiveIntensity: 1.2,
      envMap: textureCube,
      metalness: 0.4,
      roughness: 0.96,
    });
    // 透明材质
    const opacityMaterial = new THREE.MeshStandardMaterial({
      color: path.color,
      side: THREE.BackSide,
      // emissiveIntensity: 1.2,
      envMap: textureCube,
      metalness: 0.5,
      roughness: 0.96,
      transparent: true,
      opacity: 0.8,
      depthWrite: false,
    });
    const backshapes = path.toShapes(true, true);
    if (svgName == 'plant' || svgName == 'guide' || svgName == 'metope') {
      exHeight = path.userData.node.parentNode.id.split('_ex')[1] | 1;
    }
    switch (svgName) {
      case 'background':
        svgGroup.add(svgSqueezeHeight(backshapes, -4, 1, material, path));
        break;
      case 'boundary':
        svgGroup.add(svgSqueezeHeight(backshapes, -3, 3, material));
        break;
      case 'region':
        svgGroup.add(svgSqueezeHeight(backshapes, 0.5, 0, material));
        break;
      case 'lane':
        svgGroup.add(svgSqueezeHeight(backshapes, 1, 1, material));
        break;
      case 'guide':
        svgGroup.add(
          svgSqueezeHeight(backshapes, 1, exHeight, material, path, true)
        );
        break;
      case 'metope':
        svgGroup.add(
          svgSqueezeHeight(backshapes, 0, exHeight, opacityMaterial, path, true)
        );
        break;
      case 'room':
        svgGroup.add(svgSqueezeHeight(backshapes, 0, 1, material, path, true));
        break;
    }
  }
  svgGroup.add(spiritgroup);
  // if (name != '1Fgroup') {
  //   svgGroup.visible = false;
  // }
  return svgGroup;
};

const addSprite = (name, position, isText) => {
  const canvas = document.createElement('canvas');
  canvas.width = 200;
  canvas.height = 40;
  const context = canvas.getContext('2d');
  const texture = new THREE.CanvasTexture(canvas);
  // context.fillStyle = "#fff"; // 背景颜色
  // context.fillRect(0, 0, 220, 200);
  if (isText) {
    context.lineWidth = 5;
    context.font = '28px Arial';
    context.strokeStyle = '#ffffff';
    context.textAlign = 'left';
    context.textBaseline = 'middle'; // 中间线
    context.strokeText(name, 44, 20);
    context.font = '28px Arial';
    context.fillStyle = '#333';
    context.textAlign = 'left'; // 对齐方式
    context.textBaseline = 'middle'; // 中间线
    context.fillText(name, 44, 20);
    texture.needsUpdate = true;
  } else {
    var img = new Image();
    img.src = `img/icon/icon_${name}.png`;
    img.onload = function () {
      context.drawImage(img, 0, 0, 40, 40);
      // 文字描边
      context.lineWidth = 5;
      context.font = '28px Arial';
      context.strokeStyle = '#ffffff';
      context.textAlign = 'left';
      context.textBaseline = 'middle'; // 中间线
      context.strokeText(name, 44, 20);
      context.font = '28px Arial';
      context.fillStyle = '#333';
      context.textAlign = 'left'; // 对齐方式
      context.textBaseline = 'middle'; // 中间线
      context.fillText(name, 44, 20);
      texture.needsUpdate = true;
    };
  }
  const spriteMaterial = new THREE.SpriteMaterial({
    map: texture, //设置精灵纹理贴图
    transparent: true,
    depthWrite: false,
    // depthTest: false,
    sizeAttenuation: false,
  });
  // 创建精灵模型对象
  let sprite = new THREE.Sprite(spriteMaterial);
  sprite.name = name;
  sprite.renderOrder = 1;
  sprite.scale.set(0.15, 0.03, 0.0);
  if (isText) {
    sprite.center.set(0.3, 0);
    sprite.position.set(position.x, 46, position.z);
  } else {
    sprite.position.set(position.x, 46, position.z);
    sprite.center.set(0.02, 0);
  }
  return sprite;
};
// 获取相应的attrbute属性,进行解析,然后转换为position对象,与朝向
const svgAttrbute = (svg) => {
  if (svg.length > 0) {
    let textPosition;
    let regex = /\((.+?)\)/g;
    let options = svg[0].value.match(regex)[0];
    const matrixNum = options.substring(1, options.length - 1).split(' ');
    textPosition = {
      xup: Number(matrixNum[0]),
      yup: Number(matrixNum[1]),
      zup: Number(matrixNum[2]),
      x: Number(matrixNum[4]),
      y: Number(matrixNum[3]),
      z: Number(matrixNum[5]),
    };
    return textPosition;
  }
};

// shaps的设置高度等参数
const heightSetting = (height) => {
  const setting = {
    steps: 1,
    depth: -height,
    bevelEnabled: false,
    bevelThickness: 1,
    bevelSize: 1,
    bevelOffset: 0,
    bevelSegments: 1,
  };
  return setting;
};

export { svgToModel };
